package com.ytjj.quartz.service;

import com.ytjj.common.exception.ApiException;
import com.ytjj.qmyx.mall.model.PlatformStatistics;
import com.ytjj.qmyx.mall.model.UsersAnalysis;
import com.ytjj.qmyx.users.model.UsersActive;
import com.ytjj.quartz.constants.PlatformStatisticsConstant;
import com.ytjj.quartz.dao.OrdersDao;
import com.ytjj.quartz.dao.PlatformStatisticsDao;
import com.ytjj.quartz.dao.UsersDao;
import com.ytjj.quartz.model.PayStatisticsResponse;
import com.ytjj.quartz.model.StatisticsUserResponse;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.math.BigDecimal;
import java.util.Date;
import java.util.List;
import java.util.Optional;

/**
 * 
 * 
 * @Version 1.0
 **/
@Service
@Slf4j
public class PlatformStatisticsService {

    @Resource
    private UsersDao usersDao;

    @Resource
    private OrdersDao ordersDao;

    @Resource
    private PlatformStatisticsDao platformStatisticsDao;

    /**
     * 平台统计数据信息
     * @param startTime
     * @param endTime
     */
    @Transactional(rollbackFor = Exception.class)
    public void selPlatformInfo(String startTime, String endTime, String operation) {

        //创建PlatformStatistics对象
        PlatformStatistics iosPlatform = new PlatformStatistics();
        iosPlatform.setSource("ios");
        PlatformStatistics androidPlatform = new PlatformStatistics();
        androidPlatform.setSource("android");
        PlatformStatistics weappPlatform = new PlatformStatistics();
        weappPlatform.setSource("weapp");
        PlatformStatistics h5Platform = new PlatformStatistics();
        h5Platform.setSource("h5");

        //日活跃人数
        List<UsersAnalysis> iosDaus = usersDao.getActiveUser(startTime, endTime, PlatformStatisticsConstant.PLATFORM_IOS);
        List<UsersAnalysis> androidDaus = usersDao.getActiveUser(startTime, endTime, PlatformStatisticsConstant.PLATFORM_ANDROID);
        List<UsersAnalysis> weappDaus = usersDao.getActiveUser(startTime, endTime, PlatformStatisticsConstant.PLATFORM_WEAPP);
        List<UsersAnalysis> h5Daus = usersDao.getActiveUser(startTime, endTime, PlatformStatisticsConstant.PLATFORM_H5);
        iosPlatform.setDaus(iosDaus.size());
        androidPlatform.setDaus(androidDaus.size());
        weappPlatform.setDaus(weappDaus.size());
        h5Platform.setDaus(h5Daus.size());

        //新增用户
        List<StatisticsUserResponse> iosAddUser = usersDao.getAddUser(startTime, endTime, PlatformStatisticsConstant.PLATFORM_IOS);
        List<StatisticsUserResponse> androidAddUser = usersDao.getAddUser(startTime, endTime, PlatformStatisticsConstant.PLATFORM_ANDROID);
        List<StatisticsUserResponse> weappAddUser = usersDao.getAddUser(startTime, endTime, PlatformStatisticsConstant.PLATFORM_WEAPP);
        List<StatisticsUserResponse> h5AddUser = usersDao.getAddUser(startTime, endTime, PlatformStatisticsConstant.PLATFORM_H5);
        iosPlatform.setNewUser(iosAddUser.size());
        androidPlatform.setNewUser(androidAddUser.size());
        weappPlatform.setNewUser(weappAddUser.size());
        h5Platform.setNewUser(h5AddUser.size());

        //激活用户
        List<UsersActive> iosActivityUsers = usersDao.getActiveUsersByPlat(startTime, endTime, PlatformStatisticsConstant.PLATFORM_IOS);
        List<UsersActive> androidActivityUsers = usersDao.getActiveUsersByPlat(startTime, endTime, PlatformStatisticsConstant.PLATFORM_ANDROID);
        List<UsersActive> weappActivityUsers = usersDao.getActiveUsersByPlat(startTime, endTime, PlatformStatisticsConstant.PLATFORM_WEAPP);
        List<UsersActive> h5ActivityUsers = usersDao.getActiveUsersByPlat(startTime, endTime, PlatformStatisticsConstant.PLATFORM_H5);
        iosPlatform.setActiveUser(iosActivityUsers.size());
        androidPlatform.setActiveUser(androidActivityUsers.size());
        weappPlatform.setActiveUser(weappActivityUsers.size());
        h5Platform.setActiveUser(h5ActivityUsers.size());

        //新用户首下单数
        Integer iosFirstBuyNum = Optional.ofNullable(ordersDao.getFirstBugNum(PlatformStatisticsConstant.PLATFORM_IOS, startTime, endTime))
                .orElseGet(() -> 0);
        Integer androidFirstBuyNum = Optional.ofNullable(ordersDao.getFirstBugNum(PlatformStatisticsConstant.PLATFORM_ANDROID, startTime, endTime))
                .orElseGet(() -> 0);
        Integer weappFirstBuyNum = Optional.ofNullable(ordersDao.getFirstBugNum(PlatformStatisticsConstant.PLATFORM_WEAPP, startTime, endTime))
                .orElseGet(() -> 0);
        Integer h5FirstBuyNum = Optional.ofNullable(ordersDao.getFirstBugNum(PlatformStatisticsConstant.PLATFORM_H5, startTime, endTime))
                .orElseGet(() -> 0);
        iosPlatform.setFirstBuyNum(iosFirstBuyNum);
        androidPlatform.setFirstBuyNum(androidFirstBuyNum);
        weappPlatform.setFirstBuyNum(weappFirstBuyNum);
        h5Platform.setFirstBuyNum(h5FirstBuyNum);

        //订单数
        List<PayStatisticsResponse> iosOrdersCount = ordersDao.getOrdersCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_IOS);
        List<PayStatisticsResponse> androidOrdersCount = ordersDao.getOrdersCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_ANDROID);
        List<PayStatisticsResponse> weappOrdersCount = ordersDao.getOrdersCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_WEAPP);
        List<PayStatisticsResponse> h5OrdersCount = ordersDao.getOrdersCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_H5);
        iosPlatform.setOrderNum(iosOrdersCount.size());
        androidPlatform.setOrderNum(androidOrdersCount.size());
        weappPlatform.setOrderNum(weappOrdersCount.size());
        h5Platform.setOrderNum(h5OrdersCount.size());

        //实际订单数
        List<PayStatisticsResponse> iosRealOrdersCount = ordersDao.getRealOrdersCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_IOS);
        List<PayStatisticsResponse> androidRealOrdersCount = ordersDao.getRealOrdersCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_ANDROID);
        List<PayStatisticsResponse> weappRealOrdersCount = ordersDao.getRealOrdersCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_WEAPP);
        List<PayStatisticsResponse> h5RealOrdersCount = ordersDao.getRealOrdersCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_H5);
        iosPlatform.setRealOrderNum(iosRealOrdersCount.size());
        androidPlatform.setRealOrderNum(androidRealOrdersCount.size());
        weappPlatform.setRealOrderNum(weappRealOrdersCount.size());
        h5Platform.setRealOrderNum(h5RealOrdersCount.size());

        //支付订单数
        List<PayStatisticsResponse> iosPayOrdersCount = ordersDao.getPayOrdersCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_IOS);
        List<PayStatisticsResponse> androidPayOrdersCount = ordersDao.getPayOrdersCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_ANDROID);
        List<PayStatisticsResponse> weappPayOrdersCount = ordersDao.getPayOrdersCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_WEAPP);
        List<PayStatisticsResponse> h5PayOrdersCount = ordersDao.getPayOrdersCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_H5);
        iosPlatform.setPayNum(iosPayOrdersCount.size());
        androidPlatform.setPayNum(androidPayOrdersCount.size());
        weappPlatform.setPayNum(weappPayOrdersCount.size());
        h5Platform.setPayNum(h5PayOrdersCount.size());

        //支付率
        BigDecimal iosPayRation = BigDecimal.ZERO;
        if(iosOrdersCount.size() != 0) {
            iosPayRation = BigDecimal.valueOf(iosPayOrdersCount.size()).divide(BigDecimal.valueOf(iosOrdersCount.size()), 4, BigDecimal.ROUND_DOWN);
        }
        iosPlatform.setPayRatio(iosPayRation + "");
        BigDecimal androidPayRation = BigDecimal.ZERO;
        if(androidOrdersCount.size() != 0) {
            androidPayRation = BigDecimal.valueOf(androidPayOrdersCount.size()).divide(BigDecimal.valueOf(androidOrdersCount.size()), 4, BigDecimal.ROUND_DOWN);
        }
        androidPlatform.setPayRatio(androidPayRation + "");
        BigDecimal weappPayRation = BigDecimal.ZERO;
        if(weappOrdersCount.size() != 0) {
            weappPayRation = BigDecimal.valueOf(weappPayOrdersCount.size()).divide(BigDecimal.valueOf(weappOrdersCount.size()), 4, BigDecimal.ROUND_DOWN);
        }
        weappPlatform.setPayRatio(weappPayRation + "");
        BigDecimal h5PayRation = BigDecimal.ZERO;
        if(h5PayOrdersCount.size() > 0 && h5OrdersCount.size() > 0) {
            h5PayRation = BigDecimal.valueOf(h5PayOrdersCount.size()).divide(BigDecimal.valueOf(h5OrdersCount.size()), 4, BigDecimal.ROUND_DOWN);
        }
        h5Platform.setPayRatio(h5PayRation + "");

        //支付金额
        BigDecimal iosPayMoney = ordersDao.getPayMoney(startTime, endTime, PlatformStatisticsConstant.PLATFORM_IOS);
        if(iosPayMoney == null) {
            iosPayMoney = BigDecimal.ZERO;
        }
        BigDecimal androidPayMoney = ordersDao.getPayMoney(startTime, endTime, PlatformStatisticsConstant.PLATFORM_ANDROID);
        if(androidPayMoney == null) {
            androidPayMoney = BigDecimal.ZERO;
        }
        BigDecimal weappPayMoney = ordersDao.getPayMoney(startTime, endTime, PlatformStatisticsConstant.PLATFORM_WEAPP);
        if(weappPayMoney == null) {
            weappPayMoney = BigDecimal.ZERO;
        }
        BigDecimal h5PayMoney = ordersDao.getPayMoney(startTime, endTime, PlatformStatisticsConstant.PLATFORM_H5);
        if(h5PayMoney == null) {
            h5PayMoney = BigDecimal.ZERO;
        }
        iosPlatform.setPayMoney(iosPayMoney);
        androidPlatform.setPayMoney(androidPayMoney);
        weappPlatform.setPayMoney(weappPayMoney);
        h5Platform.setPayMoney(h5PayMoney);

        //成本
        BigDecimal iosCostMoney = ordersDao.getCostAmount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_IOS);
        if(iosCostMoney == null) {
            iosCostMoney = BigDecimal.ZERO;
        }
        BigDecimal androidCostMoney = ordersDao.getCostAmount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_ANDROID);
        if(androidCostMoney == null) {
            androidCostMoney = BigDecimal.ZERO;
        }
        BigDecimal weappCostMoney = ordersDao.getCostAmount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_WEAPP);
        if(weappCostMoney == null) {
            weappCostMoney = BigDecimal.ZERO;
        }
        BigDecimal h5CostMoney = ordersDao.getCostAmount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_H5);
        if(h5CostMoney == null) {
            h5CostMoney = BigDecimal.ZERO;
        }
        iosPlatform.setCostMoney(iosCostMoney);
        androidPlatform.setCostMoney(androidCostMoney);
        weappPlatform.setCostMoney(weappCostMoney);
        h5Platform.setCostMoney(h5CostMoney);

        //利润
        BigDecimal iosProfit = BigDecimal.ZERO;
        if (iosPayMoney != null && iosCostMoney !=null) {
            iosProfit = iosPayMoney.subtract(iosCostMoney).setScale(2, BigDecimal.ROUND_DOWN);
        }
        BigDecimal androidProfit = BigDecimal.ZERO;
        if (androidPayMoney != null && androidCostMoney != null) {
            androidProfit = androidPayMoney.subtract(androidCostMoney).setScale(2, BigDecimal.ROUND_DOWN);
        }
        BigDecimal weappProfit = BigDecimal.ZERO;
        if (weappPayMoney != null && weappCostMoney != null) {
            weappProfit = weappPayMoney.subtract(weappCostMoney).setScale(2, BigDecimal.ROUND_DOWN);
        }
        BigDecimal h5Profit = BigDecimal.ZERO;
        if (h5PayMoney != null && h5CostMoney != null) {
            h5Profit = h5PayMoney.subtract(h5CostMoney).setScale(2, BigDecimal.ROUND_DOWN);
        }
        iosPlatform.setProfit(iosProfit);
        androidPlatform.setProfit(androidProfit);
        weappPlatform.setProfit(weappProfit);
        h5Platform.setProfit(h5Profit);

        //订单率 订单数/日活跃人数
        BigDecimal iosOrderRatio = BigDecimal.ZERO;
        if (iosDaus.size() != 0) {
            Integer a = iosRealOrdersCount.size();
            Integer b = iosDaus.size();
            iosOrderRatio = BigDecimal.valueOf(a.longValue()).divide(BigDecimal.valueOf(b.longValue()), 4, BigDecimal.ROUND_DOWN);
        }
        iosPlatform.setOrderRatio(iosOrderRatio + "");
        BigDecimal androidOrderRatio = BigDecimal.ZERO;
        if (androidDaus.size() != 0) {
            Integer a = androidRealOrdersCount.size();
            Integer b = androidDaus.size();
            androidOrderRatio = BigDecimal.valueOf(a.longValue()).divide(BigDecimal.valueOf(b.longValue()), 4, BigDecimal.ROUND_DOWN);
        }
        androidPlatform.setOrderRatio(androidOrderRatio + "");
        BigDecimal weappOrderRatio = BigDecimal.ZERO;
        if (weappDaus.size() != 0) {
            Integer a = weappRealOrdersCount.size();
            Integer b = weappDaus.size();
            weappOrderRatio = BigDecimal.valueOf(a.longValue()).divide(BigDecimal.valueOf(b.longValue()), 4, BigDecimal.ROUND_DOWN);
        }
        weappPlatform.setOrderRatio(weappOrderRatio + "");
        BigDecimal h5OrderRatio = BigDecimal.ZERO;
        if (h5Daus.size() != 0) {
            Integer a = h5RealOrdersCount.size();
            Integer b = h5Daus.size();
            h5OrderRatio = BigDecimal.valueOf(a.longValue()).divide(BigDecimal.valueOf(b.longValue()), 4, BigDecimal.ROUND_DOWN);
        }
        h5Platform.setOrderRatio(h5OrderRatio + "");

        //客单率 支付金额/支付数
        BigDecimal iosCustomerRatio = BigDecimal.ZERO;
        if (iosPayOrdersCount.size() > 0) {
            Integer a = iosPayOrdersCount.size();
            iosCustomerRatio = iosPayMoney.divide(BigDecimal.valueOf(a.longValue()), 2, BigDecimal.ROUND_DOWN);
        }
        iosPlatform.setCustomerRatio(iosCustomerRatio + "");
        BigDecimal androidCustomerRatio = BigDecimal.ZERO;
        if (androidPayOrdersCount.size() > 0) {
            Integer a = androidPayOrdersCount.size();
            androidCustomerRatio = androidPayMoney.divide(BigDecimal.valueOf(a.longValue()), 2, BigDecimal.ROUND_DOWN);
        }
        androidPlatform.setCustomerRatio(androidCustomerRatio + "");
        BigDecimal weappCustomerRatio = BigDecimal.ZERO;
        if (weappPayOrdersCount.size() > 0) {
            Integer a = weappPayOrdersCount.size();
            weappCustomerRatio = weappPayMoney.divide(BigDecimal.valueOf(a.longValue()), 2, BigDecimal.ROUND_DOWN);
        }
        weappPlatform.setCustomerRatio(weappCustomerRatio + "");
        BigDecimal h5CustomerRatio = BigDecimal.ZERO;
        if (h5PayOrdersCount.size() > 0) {
            Integer a = h5PayOrdersCount.size();
            h5CustomerRatio = h5PayMoney.divide(BigDecimal.valueOf(a.longValue()), 2, BigDecimal.ROUND_DOWN);
        }
        h5Platform.setCustomerRatio(h5CustomerRatio + "");

        //点击地址数
        Integer iosClickNum = usersDao.getAddressClickCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_IOS).size();
        Integer androidClickNum = usersDao.getAddressClickCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_ANDROID).size();
        Integer weappClickNum = usersDao.getAddressClickCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_WEAPP).size();
        Integer h5ClickNum = usersDao.getAddressClickCount(startTime, endTime, PlatformStatisticsConstant.PLATFORM_H5).size();
        iosPlatform.setAddressClickNum(iosClickNum);
        androidPlatform.setAddressClickNum(androidClickNum);
        weappPlatform.setAddressClickNum(weappClickNum);
        h5Platform.setAddressClickNum(h5ClickNum);

        if (operation.equals("fiveFlush")) {
            //每五分钟执行一次数据刷新
            PlatformStatistics iosPlat = platformStatisticsDao.getStatistics("ios");

            if (null != iosPlat) {
                iosPlatform.setId(iosPlat.getId());
                iosPlatform.setRecordTime(new Date());
                platformStatisticsDao.updatePlatform(iosPlatform);
            } else {
                iosPlatform.setCreateTime(new Date());
                iosPlatform.setRecordTime(new Date());
                platformStatisticsDao.insertPlatform(iosPlatform);
            }

            PlatformStatistics androidPlat = platformStatisticsDao.getStatistics("android");
            if (null != androidPlat) {
                androidPlatform.setId(androidPlat.getId());
                androidPlatform.setRecordTime(new Date());
                platformStatisticsDao.updatePlatform(androidPlatform);
            } else {
                androidPlatform.setCreateTime(new Date());
                androidPlatform.setRecordTime(new Date());
                platformStatisticsDao.insertPlatform(androidPlatform);
            }

            PlatformStatistics weappPlat = platformStatisticsDao.getStatistics("weapp");
            if (null != weappPlat) {
                weappPlatform.setId(weappPlat.getId());
                weappPlatform.setRecordTime(new Date());
                platformStatisticsDao.updatePlatform(weappPlatform);
            } else {
                weappPlatform.setCreateTime(new Date());
                weappPlatform.setRecordTime(new Date());
                platformStatisticsDao.insertPlatform(weappPlatform);
            }

            PlatformStatistics h5Plat = platformStatisticsDao.getStatistics("h5");
            if (null != h5Plat) {
                h5Platform.setId(h5Plat.getId());
                h5Platform.setRecordTime(new Date());
                platformStatisticsDao.updatePlatform(h5Platform);
            } else {
                h5Platform.setCreateTime(new Date());
                h5Platform.setRecordTime(new Date());
                platformStatisticsDao.insertPlatform(h5Platform);
            }
        } else if (operation.equals("onlyTwoFlush")) {
            iosPlatform.setRecordTime(new Date());
            platformStatisticsDao.flushPlatform(iosPlatform);

            androidPlatform.setRecordTime(new Date());
            platformStatisticsDao.flushPlatform(androidPlatform);

            weappPlatform.setRecordTime(new Date());
            platformStatisticsDao.flushPlatform(weappPlatform);

            h5Platform.setRecordTime(new Date());
            platformStatisticsDao.flushPlatform(h5Platform);
        } else {
            throw new ApiException("平台统计定时器出现异常，请检查！");
        }

    }

}
